package com.jaks.xpense.data;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.os.Environment;

import com.jaks.xpense.data.entities.Expense;
import com.jaks.xpense.data.entities.ExpenseTag;
import com.jaks.xpense.data.entities.Income;
import com.jaks.xpense.data.entities.PaymentType;
import com.jaks.xpense.data.entities.Tag;
import com.jaks.xpense.utils.Globals;

public class XpenseDatabase extends SQLiteOpenHelper {

	private static final String CreateTable = "Create Table ";

	public XpenseDatabase(Context context) {
		super(context, Globals.DatabaseName, null, Globals.DatabaseVersion);
	}

	@Override
	public void onCreate(SQLiteDatabase database) {
		String createTags = CreateTable + Tag.TableName
		    + "(_id integer primary key autoincrement, tagOrder integer not null,  name text not null)";
		String createPaymentTypes = CreateTable + PaymentType.TableName
		    + "(_id integer primary key autoincrement, name text not null)";
		String createExpenses = CreateTable
		    + Expense.TableName
		    + "(_id integer primary key autoincrement, expensedate integer not null, paymenttype integer not null, amount real not null, comments text)";
		String createExpenseTags = CreateTable
		    + ExpenseTag.TableName
		    + "(expenseId integer not null, tagId integer not null, constraint expenseTags_pk primary key(expenseId, tagId))";
		String createIncomes = CreateTable
		    + Income.TableName
		    + "(_id integer primary key autoincrement, incomedate integer not null, paymenttype integer not null, amount real not null, comments text)";

		database.execSQL(createTags);
		database.execSQL(createPaymentTypes);
		database.execSQL(createExpenses);
		database.execSQL(createExpenseTags);
		database.execSQL(createIncomes);

		database.execSQL("INSERT INTO paymenttypes (name) VALUES ('Cash') ");
		database.execSQL("INSERT INTO paymenttypes (name) VALUES ('Credit Card') ");
		database.execSQL("INSERT INTO paymenttypes (name) VALUES ('Debit Card') ");
		database.execSQL("INSERT INTO paymenttypes (name) VALUES ('Cheque') ");
		database.execSQL("INSERT INTO paymenttypes (name) VALUES ('Wire Transfer') ");
	}

	@Override
	public void onUpgrade(SQLiteDatabase database, int oldVersion, int newVersion) {
		if (newVersion == 2) {
			String createIncomes = CreateTable
			    + Income.TableName
			    + "(_id integer primary key autoincrement, incomedate integer not null, paymenttype integer not null, amount real not null, comments text)";

			database.execSQL(createIncomes);
		}
	}

	/**
	 * Copies the database file at the specified location over the current
	 * internal application database.
	 * */
	public boolean restoreDatabase(String path) throws IOException {

		// Close the SQLiteOpenHelper so it will commit the created empty
		// database to internal storage.
		close();
		File newDb = new File(path);
		File oldDb = new File(getDatabasePath());
		if (newDb.exists()) {
			Globals.copyFile(new FileInputStream(newDb), new FileOutputStream(oldDb));
			// Access the copied database so SQLiteHelper will cache it and mark
			// it as created.
			getWritableDatabase().close();
			return true;
		}
		return false;
	}

	public boolean backupDatabase(String path) throws IOException {

		// Close the SQLiteOpenHelper so it will commit the created empty
		// database to internal storage.
		close();
		File newDb = new File(path);
		File oldDb = new File(getDatabasePath());
		if (oldDb.exists()) {
			Globals.copyFile(new FileInputStream(oldDb), new FileOutputStream(newDb));
			getWritableDatabase().close();
			return true;
		}
		return false;
	}

	private String getDatabasePath() {

		File data = Environment.getDataDirectory();
		String databasePath = "/data/com.jaks.xpense/databases/" + Globals.DatabaseName;
		File dbFile = new File(data, databasePath);
		return dbFile.getAbsolutePath();
	}
}
